package com.jlcloud.core.xss.processor;

import com.jlcloud.core.xss.JlCloudXssProperties;
import com.jlcloud.core.xss.JlCloudXssProperties.Mode;
import com.jlcloud.core.xss.XssType;
import com.jlcloud.core.xss.XssUtil;
import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
import org.jsoup.nodes.Entities;
import org.springframework.util.StringUtils;
import org.springframework.web.util.HtmlUtils;

import java.nio.charset.StandardCharsets;

/**
 * 默认的 xss 清理器
 *
 * @author By: JlCloud <br>
 * @Package: com.jlcloud <br>
 * @CreateTime: 2024-12-03 21:45 <br>
 * @Copyright: 2021 www.jilianjituan.com Inc. All rights reserved. <br>
 * @Caution 注意：本内容仅限于冀联人力集团内部传阅，禁止外泄以及用于其他的商业目的 <br>
 */
public class DefaultXssCleaner implements XssCleaner {
	private final JlCloudXssProperties properties;

	public DefaultXssCleaner(JlCloudXssProperties properties) {
		this.properties = properties;
	}

	private static Document.OutputSettings getOutputSettings(JlCloudXssProperties properties) {
		return new Document.OutputSettings()
			// 转义
			.escapeMode(Entities.EscapeMode.xhtml)
			// 保留换行
			.prettyPrint(properties.isPrettyPrint());
	}

	@Override
	public String clean(String name, String bodyHtml, XssType type) {
		// 为空直接返回
		if (!StringUtils.hasText(bodyHtml)) {
			return bodyHtml;
		}
		Mode mode = properties.getMode();
		if (Mode.ESCAPE == mode) {
			// html 转义
			return HtmlUtils.htmlEscape(bodyHtml, StandardCharsets.UTF_8.name());
		} else if (Mode.VALIDATE == mode) {
			// 校验
			if (Jsoup.isValid(bodyHtml, XssUtil.SAFE_LIST)) {
				return bodyHtml;
			}
			throw type.getXssException(name, bodyHtml, "Xss validate fail, input value:" + bodyHtml);
		} else {
			if (properties.isEnableEscape()) {
				// 转义
				bodyHtml = Entities.escape(bodyHtml);
			} else {
				// 反转义
				bodyHtml = Entities.unescape(bodyHtml);
			}
			return XssUtil.clean(bodyHtml, getOutputSettings(properties));
		}
	}

}
